// ts type chanllge

export type LegthOfTuple<T extends any[]> = T['length']
type A = LegthOfTuple<[1, 2, 3]>

export type FirstItem<T extends any[]> = T[0]
type B = FirstItem<[]>

export type ListItem<T extends any[]> = T extends [...any, infer I] ? I : never
type C = ListItem<[1, 2, 3]>

export type Shift<T extends any[]> = T extends [infer R,  ...infer B] ? B : T
type D = Shift<[1, 2, 3]>

export type Push<T extends any[], U> = [...T, U]
type E = Push<[1, 2, 3], 4>

export type ReverseTuple<T extends any[], F extends any[] = []> =
  T extends [infer L, ...infer R] ? ReverseTuple<R,  [L, ...F]> : F
type F = ReverseTuple<[1, 2, 3, 4]>

// 这个要好好想想
export type Flat<T extends any[], F extends any[] = []> = T extends [infer L, ...infer R] ?
[
  ...(L extends any[] ? Flat<L> : [L]),
  ...Flat<R>
] : []
type G = Flat<[1, 2, 3, [5, 6]]>

type Repeat<T extends any, C extends number, F extends any[] = []> =C extends F['length']
  ? F 
  : Repeat<T, C, [...F, T]>
type H = Repeat<number, 2>

type Filter<T extends any[], A, F extends any[] = []> = T extends [infer L, ...infer R]
  ? L extends A ? Filter<R, A, [...F, L]> : Filter<R, A, F>
  : F
type I = Filter<[1, 2, 'a', 'b', true, 3], number>
type U = Filter<[1, 2, 'a', 'b', any, true, 3], number> // any会分发

type isEqueal<T, U, Succ, Fail> = [T] extends [U]
  ? [U] extends [T]
    ? Succ
    : Fail
  : Fail

type T3 = isEqueal<string, number, true, false>
type FindIndex<T extends any[], V, F extends any[] = []> = T extends [infer L, ...infer R]
  ? isEqueal<L, V, F['length'], FindIndex<R, V, [...F, never]>>
  : never
type T1 = [string, number, 1, 'a', any]
type T2 = FindIndex<T1, 1>

type TupleToMenu<T extends any[], needIdx extends boolean = false> = {
  [K in T[number]]: needIdx extends true ? FindIndex<T, K> : K
}
type T4 = TupleToMenu<['a', 'b', 'c'], true>

type Slice<
  T extends any[],
  S extends number,
  E extends number = T['length'],
  SA extends any[] = [],
  EA extends any[] = [],
  F extends any[] = []> = T extends [infer L, ...infer R]
  ? SA['length'] extends S
    ? EA['length'] extends E 
      ? [...F, L]
      : Splice<R, S, E, SA, [...EA, never], [...F, L]>
    : Splice<R, S, E, [...SA, never], [...EA, never], F>
  : F
type T5 = Slice<['a', 'b', 'c', 1, 2, true, false], 0 ,1>


type Splice<
  T extends any[],
  S extends number,
  E extends number,
  I extends any[],
  SA extends any [] = [],
  C extends any [] = [], // 记录删除的个数
  F extends any[] = []
> = T extends [infer L, ...infer R]
  ? SA['length'] extends S
    ? C['length'] extends E
      ? [...F, ...I, ...T]
      : Splice<R, S, E, I, SA, [...C, null], F>
    : Splice<R, S, E, I, [...SA, null], C, [...F, L]>
  : F


type T6 = Splice<[1, 2, 3, true, false, 'a'], 1, 2, [12, 'abc']>

export {}